﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using System.Xml;

namespace CheatEngineTableTranslation
{
	internal static class FileOperate
	{
		private static Dictionary<string, string> DataByReadCTFile = new Dictionary<string, string>();

		private static Dictionary<string, string> DataByReadTranslate = new Dictionary<string, string>();

		private static int ValidCountByReadCTFile = 0;

		private static int ValidCountByReadTranslate = 0;

		public static string LocalTranslation(RichTextBox richTextBox2)
		{
			if (DataByReadCTFile.Count == 0)
			{
				return "需要翻译字典的条目为空！";
			}
			richTextBox2.Text = string.Empty;
			ReadTranslateByCSVFile reader = new ReadTranslateByCSVFile();

			if (reader.ReadResult)
			{
				// 用于保存更新后的内容
				List<string> updatedContent = new List<string>();

				foreach (var entry in DataByReadCTFile)
				{
					string key = entry.Key; // 字典中的 key
					string original = entry.Value; // 字典中的值作为原文

					// 使用 GetTranslationsByOriginal 查找译文
					var translations = reader.GetTranslationsByOriginal(original);
					string translation = translations.Count > 0 ? translations[0].Translation : original;

					// 格式化内容
					updatedContent.Add($"{key},{translation}");
				}

				// 更新 RichTextBox 内容
				richTextBox2.Text = string.Join(Environment.NewLine, updatedContent);
				return "本地翻译成功！";
			}
			else
			{
				return reader.Error;
			}
		}

		public static string ReadCTFile(string ctFilePath, RichTextBox richTextBox1)
		{
			ReadCTFile readCTFile = new ReadCTFile(ctFilePath, richTextBox1);
			DataByReadCTFile.Clear();
			DataByReadCTFile = readCTFile.ReadData;
			ValidCountByReadCTFile = readCTFile.validCount;
			return readCTFile.readResult;
		}

		public static string ReadTranslateByRTB(RichTextBox richTextBox2)
		{
			ReadTranslateByRichTextBox readTranslate = new ReadTranslateByRichTextBox(richTextBox2);
			DataByReadTranslate.Clear();
			DataByReadTranslate = readTranslate.ReadData;
			ValidCountByReadTranslate = readTranslate.validCount;
			return readTranslate.readResult;
		}

		public static string SaveTranslations()
		{
			if (DataByReadTranslate.Count != DataByReadCTFile.Count || DataByReadCTFile.Count == 0 || DataByReadTranslate.Count == 0)
			{
				return "字典的条目数量不匹配，无法保存翻译！";
			}

			List<SavaTranslate> saveTranslateResults = new List<SavaTranslate>();

			foreach (var key in DataByReadCTFile.Keys)
			{
				if (DataByReadTranslate.ContainsKey(key))
				{
					string original = DataByReadCTFile[key];
					string translation = DataByReadTranslate[key];
					SavaTranslate saveTranslate = new SavaTranslate(original, translation);
					saveTranslateResults.Add(saveTranslate);
				}
				else
				{
					return $"字典中的key '{key}' 在译文字典中找不到对应项！";
				}
			}
			return "翻译保存成功！";
		}

		public static string ErrorByWriteCTFile = string.Empty;
		public static List<string> errorMessages = new List<string>();  // 用来收集错误信息

		public static bool WriteCTFiles(string ctFilePath)
		{
			try
			{
				// Step 1: 检查文件是否存在
				if (!File.Exists(ctFilePath))
				{
					ErrorByWriteCTFile = "文件未找到。";
					return false;
				}

				// Step 2: 备份文件
				string backupFilePath = ctFilePath + ".bak";
				File.Copy(ctFilePath, backupFilePath, true);

				// Step 3: 读取文件内容
				string[] fileLines = File.ReadAllLines(ctFilePath, Encoding.UTF8);

				// Step 4: 修改文件内容
				foreach (var entry in DataByReadTranslate)
				{
					string id = entry.Key;
					string description = entry.Value;

					bool idFound = false;

					for (int i = 0; i < fileLines.Length; i++)
					{
						// 精确匹配 <ID> 元素
						if (Regex.IsMatch(fileLines[i], $@"<ID>\s*{id}\s*</ID>"))
						{
							idFound = true;

							// 替换 <Description> 元素
							for (int j = i; j < fileLines.Length; j++)
							{
								if (Regex.IsMatch(fileLines[j], @"<Description>.*?</Description>"))
								{
									// 使用正则替换 <Description> 的内容
									fileLines[j] = Regex.Replace(
										fileLines[j],
										"(<Description>).*?(</Description>)",
										$"$1{description}$2"
									);
									break;
								}
							}

							break; // 跳出外层循环，避免误匹配其他 ID
						}
					}

					if (!idFound)
					{
						errorMessages.Add($"未找到匹配的ID: {id}");
					}
				}

				// Step 5: 写回文件
				File.WriteAllLines(ctFilePath, fileLines, new UTF8Encoding(false));

				// 如果有错误信息，返回失败
				if (errorMessages.Count > 0)
				{
					ErrorByWriteCTFile = string.Join(Environment.NewLine, errorMessages);
					return false;
				}

				ErrorByWriteCTFile = string.Empty;
				return true;
			}
			catch (Exception ex)
			{
				// 错误处理
				ErrorByWriteCTFile = $"发生错误: {ex.Message}";
				if (File.Exists(ctFilePath + ".bak"))
				{
					File.Copy(ctFilePath + ".bak", ctFilePath, true);
				}
				return false;
			}
		}
	}

	internal class ReadCTFile
	{
		public Dictionary<string, string> ReadData = new Dictionary<string, string>();

		public string readResult = string.Empty;

		public int validCount = 0;

		public ReadCTFile(string ctFilePath, RichTextBox richTextBox1)
		{
			if (string.IsNullOrEmpty(ctFilePath) || !File.Exists(ctFilePath) || !ctFilePath.EndsWith(".ct", StringComparison.OrdinalIgnoreCase))
			{
				readResult = "文件路径为空或文件不存在，或者不是.ct文件！";
			}

			try
			{
				// 2. 读取文件中的内容，解析XML格式
				XmlDocument xmlDoc = new XmlDocument();
				xmlDoc.Load(ctFilePath);

				// 查找所有 <CheatEntry> 节点
				XmlNodeList cheatEntries = xmlDoc.GetElementsByTagName("CheatEntry");

				// 清空 RichTextBox 用于显示更新的数据
				richTextBox1.Clear();
				StringBuilder sb = new StringBuilder();

				// 3. 处理每个 <CheatEntry> 节点，提取 ID 和 Description 信息
				foreach (XmlNode cheatEntry in cheatEntries)
				{
					XmlNode idNode = cheatEntry.SelectSingleNode("ID");
					XmlNode descriptionNode = cheatEntry.SelectSingleNode("Description");

					if (idNode != null && descriptionNode != null)
					{
						string id = idNode.InnerText.Trim();
						string description = descriptionNode.InnerText.Trim();

						// 使用正则表达式提取双引号内的内容
						string extractedDescription = ExtractDescriptionInQuotes(description);

						// 如果没有双引号内的内容，或者内容为纯数字或特殊符号，则跳过
						if (string.IsNullOrEmpty(extractedDescription) || IsPureNumber(extractedDescription) || IsSpecialSymbol(extractedDescription))
						{
							sb.AppendLine($"ID: {id} 的 Description 中没有有效内容，跳过此条目");
							continue; // 跳过当前条目
						}

						// 如果字典中不存在该 ID，则添加
						if (!ReadData.ContainsKey(id))
						{
							ReadData.Add(id, extractedDescription);
							validCount++;  // 计数有效条目
						}
						else
						{
							// 如果 ID 已经存在，可以选择跳过或覆盖
							sb.AppendLine($"ID: {id} 已经存在，跳过此条目");
						}
					}
				}

				// 将所有内容更新到 RichTextBox
				foreach (var entry in ReadData)
				{
					sb.AppendLine($"{entry.Key},{entry.Value}");
				}

				richTextBox1.Text = sb.ToString();

				// 显示统计结果
				if (validCount == 0)
				{
					readResult = "文件中没有找到有效的 CheatEntry 数据！";
				}
				else
				{
					readResult = $"数据加载成功！共找到 {validCount} 条有效数据。";
				}
			}
			catch (Exception ex)
			{
				// 如果文件解析或读取出现异常，显示错误信息
				readResult = $"错误: {ex.Message}";
			}
		}

		// 正则表达式提取双引号内的内容
		private string ExtractDescriptionInQuotes(string description)
		{
			// 匹配双引号内的内容
			var match = Regex.Match(description, "\"([^\"]*)\"");

			if (match.Success)
			{
				return match.Groups[1].Value; // 返回双引号内的内容
			}
			else
			{
				// 如果没有双引号内的内容，返回 null
				return null;
			}
		}

		// 检查是否为纯数字
		private bool IsPureNumber(string str)
		{
			return Regex.IsMatch(str, @"^\d+$");
		}

		// 检查是否包含只有特殊符号（不包含字母和数字）
		private bool IsSpecialSymbol(string str)
		{
			return Regex.IsMatch(str, @"^[^\w\s]+$");
		}
	}

	internal class ReadTranslateByCSVFile
	{
		public bool ReadResult { get; private set; } = false;
		public string Error { get; private set; } = string.Empty;
		private Dictionary<string, List<TranslationEntry>> translationDict = new Dictionary<string, List<TranslationEntry>>(StringComparer.OrdinalIgnoreCase);

		public struct TranslationEntry
		{
			public int Id;
			public string Original;
			public string Translation;

			public TranslationEntry(int id, string original, string translation)
			{
				Id = id;
				Original = original;
				Translation = translation;
			}
		}

		public ReadTranslateByCSVFile()
		{
			try
			{
				string csvFilePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Translation.csv");

				if (!File.Exists(csvFilePath))
				{
					Error = "发生错误: 翻译文件不存在！";
					ReadResult = false;
					return;
				}

				FileInfo fileInfo = new FileInfo(csvFilePath);
				if (fileInfo.Length == 0)
				{
					Error = "发生错误: 翻译文件为空！";
					ReadResult = false;
					return;
				}
				string[] lines = File.ReadAllLines(csvFilePath);

				if (lines.Length < 2 || lines[0].Trim() != "id,original,translation")
				{
					Error = "发生错误: 文件格式错误或标题行不正确！";
					ReadResult = false;
					return;
				}

				for (int i = 1; i < lines.Length; i++)
				{
					string[] parts = lines[i].Split(',');
					if (parts.Length != 3)
					{
						Error = $"发生错误: 第 {i + 1} 行格式错误！";
						ReadResult = false;
						return;
					}

					if (!int.TryParse(parts[0], out int id))
					{
						Error = $"发生错误: 第 {i + 1} 行的 ID 无效！";
						ReadResult = false;
						return;
					}

					var entry = new TranslationEntry(id, parts[1], parts[2]);

					// Add to the dictionary, grouping by "original"
					if (!translationDict.ContainsKey(parts[1]))
					{
						translationDict[parts[1]] = new List<TranslationEntry>();
					}
					translationDict[parts[1]].Add(entry);
				}

				ReadResult = true;
			}
			catch (Exception ex)
			{
				Error = $"发生错误: {ex.Message}";
				ReadResult = false;
			}
		}

		public List<TranslationEntry> GetTranslationsByOriginal(string original)
		{
			if (translationDict.TryGetValue(original, out var entries))
			{
				return entries;
			}
			return new List<TranslationEntry>(); // Return an empty list if the original is not found
		}
	}

	internal class ReadTranslateByRichTextBox
	{
		public Dictionary<string, string> ReadData = new Dictionary<string, string>();
		public string readResult = string.Empty;
		public int validCount = 0;  // 用于统计有效的条目数

		public ReadTranslateByRichTextBox(RichTextBox richTextBox2)
		{
			// 确保换行符没有被移除，并读取 RichTextBox 中的所有内容
			string[] lines = richTextBox2.Text.Split(new[] { "\r\n", "\n" }, StringSplitOptions.None);

			// 输出所有读取的行到 readResult
			/*
			readResult += "读取的所有行：\n";
			foreach (var line in lines)
			{
				readResult += $"'{line}'\n";  // 这里保留了换行符的显示
			}
			*/

			// 遍历每一行
			foreach (var line in lines)
			{
				// 清除多余的空格，确保字符串的整洁
				string trimmedLine = line.Trim();

				// 如果行不为空，进行解析
				if (!string.IsNullOrEmpty(trimmedLine))
				{
					// 检查是否包含中文逗号，如果是则替换为英文逗号
					string correctedLine = trimmedLine.Contains("，")
						? trimmedLine.Replace("，", ",")  // 如果是中文逗号，替换为英文逗号
						: trimmedLine;  // 否则不做处理

					// 输出处理后的行
					//readResult += $"处理后的行：'{correctedLine}'\n";

					// 尝试分割 id 和内容
					string[] parts = correctedLine.Split(new[] { ',' }, 2);

					if (parts.Length == 2)
					{
						string id = parts[0].Trim();
						string content = parts[1].Trim();

						// 输出分割后的 ID 和内容
						//readResult += $"分割结果：ID = '{id}', 内容 = '{content}'\n";

						// 判断 ID 是否重复
						if (ReadData.ContainsKey(id))
						{
							readResult += $"警告: ID '{id}' 已存在，未添加该行。\n";
						}
						else
						{
							// 添加到字典中
							ReadData[id] = content;
							validCount++;  // 增加有效条目计数
						}
					}
					else
					{
						// 输出格式不正确的行
						readResult += $"警告: 行格式不正确，跳过该行: '{line}'\n";
					}
				}
				else
				{
					// 输出空行被跳过的情况
					readResult += "警告: 空行已被跳过。\n";
				}
			}

			// 输出总结信息
			readResult += $"\n共处理了 {validCount} 条有效记录。\n";
		}
	}

	internal class SavaTranslate
	{
		public bool readResult = false;
		public string error = string.Empty;

		public SavaTranslate(string original, string translation)
		{
			try
			{
				string csvFilePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Translation.csv");
				string header = "id,original,translation";

				// 判断文件是否存在
				if (!File.Exists(csvFilePath))
				{
					// 创建文件并写入表头
					using (var writer = new StreamWriter(csvFilePath, false, new UTF8Encoding(true)))
					{
						writer.WriteLine(header);
					}
				}

				// 读取现有文件内容以确保没有重复的ID
				var lines = File.ReadAllLines(csvFilePath);

				// 计算新ID（现有数据行数）
				int newId = lines.Length - 1; // 减去表头行

				// 检查是否存在重复的original字符串，避免重复
				foreach (var line in lines)
				{
					var columns = line.Split(',');
					if (columns.Length > 1 && columns[1] == original)
					{
						error = "发现重复的original条目。";
						readResult = false;
						return;
					}
				}

				// 追加新数据
				using (var writer = new StreamWriter(csvFilePath, true, new UTF8Encoding(true)))
				{
					writer.WriteLine($"{newId},{original},{translation}");
				}

				readResult = true;
			}
			catch (Exception ex)
			{
				error = $"发生错误: {ex.Message}";
				readResult = false;
				Debug.WriteLine(error);
			}
		}
	}
}
